# -*- coding: utf-8 -*-
import numpy as np
from PIL import Image, ImageDraw
from sklearn.externals import joblib
import os
import pickle


model_path = './model/authcode.model'
target_path = "process_image/"
source_result = []
for title in os.listdir(target_path):
    source_result.append(title.replace('.png',''))


t2val = {}
def twoValue(image, G):
    for y in range(0, image.size[1]):
        for x in range(0, image.size[0]):
            g = image.getpixel((x, y))
            if g > G:
                t2val[(x, y)] = 1
            else:
                t2val[(x, y)] = 0

def clearNoise(image, N, Z):
    for i in range(0, Z):
        t2val[(0, 0)] = 1
        t2val[(image.size[0] - 1, image.size[1] - 1)] = 1
        for x in range(1, image.size[0] - 1):
            for y in range(1, image.size[1] - 1):
                nearDots = 0
                L = t2val[(x, y)]
                if L == t2val[(x - 1, y - 1)]:
                    nearDots += 1
                if L == t2val[(x - 1, y)]:
                    nearDots += 1
                if L == t2val[(x - 1, y + 1)]:
                    nearDots += 1
                if L == t2val[(x, y - 1)]:
                    nearDots += 1
                if L == t2val[(x, y + 1)]:
                    nearDots += 1
                if L == t2val[(x + 1, y - 1)]:
                    nearDots += 1
                if L == t2val[(x + 1, y)]:
                    nearDots += 1
                if L == t2val[(x + 1, y + 1)]:
                    nearDots += 1

                if nearDots < N:
                    t2val[(x, y)] = 1

def saveImage(filename, size):
    image = Image.new("1", size)
    draw = ImageDraw.Draw(image)
    for x in range(0, size[0]):
        for y in range(0, size[1]):
            draw.point((x, y), t2val[(x, y)])
    image.save(filename)

def smartSliceImg(img,count=5, p_w=1):
    '''
    :param img:
    :param outDir:
    :param count: 图片中有多少个图片
    :param p_w: 对切割地方多少像素内进行判断
    :return:
    '''
    # 加载图片
    image = Image.open(img)
    image = image.convert('L')
    # 降噪处理
    twoValue(image, 185)
    clearNoise(image, 3, 1)
    saveImage('./tmp/noise.jpg', image.size)
    del image
    image = Image.open('./tmp/noise.jpg')
    new_image = image.crop((45, 0, 175, 50))
    w, h = new_image.size
    pixdata = new_image.load()
    eachWidth = int(w / count)
    beforeX = 0
    for i in range(count):
        allBCount = []
        nextXOri = (i + 1) * eachWidth
        for x in range(nextXOri - p_w, nextXOri + p_w):
            if x >= w:
                x = w - 1
            if x < 0:
                x = 0
            b_count = 0
            for y in range(h):
                if pixdata[x, y] == 0:
                    b_count += 1
            allBCount.append({'x_pos': x, 'count': b_count})
        sort = sorted(allBCount, key=lambda e: e.get('count'))
        nextX = sort[0]['x_pos']
        box = (beforeX, 0, nextX, h)
        new_image.crop(box).resize((25,50)).save('tmp/' + "tmp_" + str(i) + ".png")
        beforeX = nextX

def predict_test(model):
    predict_result = []
    for q in range(100):
        pre_list = []
        y_list = []
        for i in range(0,5):
            part_path = "tmp/" + str(q) + "_" + str(i) + ".png"
            # part_path = "tmp/tmp_" + str(i) + ".png"
            pix = np.asarray(Image.open(part_path))
            pix = pix.reshape(25 * 50)
            pre_list.append(pix)
            y_list.append(part_path.split('/')[-1])
        pre_list = np.asarray(pre_list)
        y_list = np.asarray(y_list)
        result_list = model.predict(pre_list)
        print(result_list,q)
        predict_result.append(str(result_list[0] + result_list[1] + result_list[2] + result_list[3]))
        break
    return predict_result

def predict_one(img):
    model = joblib.load(model_path)
    pre_list = []
    smartSliceImg(img)
    for i in range(0, 5):
        part_path = "tmp/tmp_" + str(i) + ".png"
        pix = np.asarray(Image.open(os.path.join(part_path)))
        pix = pix.reshape(25 * 50)
        pre_list.append(pix)
    pre_list = np.asarray(pre_list)
    result_list = model.predict(pre_list)
    return ''.join(result_list)

def model_test():
    count = 0
    list_dir = os.listdir('./verify_code/')
    total = len(list_dir)
    for i in list_dir:
        pre = predict_one(os.path.join('./verify_code/',str(i)))
        if i.split('.')[0] == pre:
            count += 1
        else:
            print('>>error>> y--{},n--{}'.format(i.split('.')[0], pre))
    print('成功数:{}\n样本总数:{}\n成功率:{}'.format(count,total,(count/total)*100))

# 将模型转换成py2
def pickle_transformation_model_py2():
    with open('./model/authcode.model', 'rb') as f:
        w = pickle.load(f)
    pickle.dump(w, open('./model/authcode_py2.model', "wb"), protocol=2)

if __name__ == '__main__':
    # model = joblib.load(model_path)
    # predict_result = predict_test(model)
    # predict_one('5018.jpg')
    # model_test()
    # print(source_result)
    # print(predict_result)
    pickle_transformation_model_py2()